/*
 * EZCP_Sim_GUIDisp.c
 *
 *  Created on: Apr 23, 2011
 *      Author: Group 8
 */
#include "EZCP_Sim_Common.h"

#include "ablibs.h"
#include "abimport.h"
#include "proto.h"
#include "abwidgets.h"
#include "abdefine.h"

#include <photon/PxImage.h>
#include <math.h>
#include <photon/Pg.h>

#define MAX_DISPLAY_GANTRYs		4

void MsgGUIDisplay (u8 ui_msgid, u32 ui_data_len, msg_data_buf_t buf_data);
unsigned char nibbleSwap(unsigned char a);
int ParseBits(msg_data_buf_t buf, int Start, int Length);

//PhImage_t * ptImgCar = NULL;

PtWidget_t * wpArrLblCarBef [8];
PtWidget_t * wpArrLblCarAft [8];
PtWidget_t * wpArrLblObst 	[8];
PtWidget_t * wpArrLblID 	[8];
PtWidget_t * wpArrLblCash 	[8];
PtWidget_t * wpArrLblTkt	[8];
PtWidget_t * wpArrLblVoice	[8];
PtWidget_t * wpArrLblMnt	[8];

PtWidget_t * wpArrLblArmDN	[8];
PtWidget_t * wpArrLblArmUP	[8];
PtWidget_t * wpArrLblDisp	[8];

const PgColor_t	fillClrCAR		= Pg_YELLOW;
const PgColor_t	fillClrNOCAR	= Pg_TRANSPARENT;
const PgColor_t	fillClrOBST		= Pg_RED;
const PgColor_t	fillClrNOOBST	= Pg_TRANSPARENT;
const PgColor_t	fillClrARMDN	= Pg_RED;
const PgColor_t	fillClrNOARMDN	= Pg_TRANSPARENT;
const PgColor_t	fillClrARMUP	= Pg_GREEN;
const PgColor_t	fillClrNOARMUP	= Pg_TRANSPARENT;
const PgColor_t	fillPRESSED		= Pg_YELLOW;
const PgColor_t	fillNOTPRESSED	= Pg_TRANSPARENT;

void initWidgetArrays ()
{
	////////// S -> G	//////////
	wpArrLblCarBef	[0] = ABW_PtLblCarBef1;
	wpArrLblCarBef	[1] = ABW_PtLblCarBef2;
	wpArrLblCarBef	[2] = ABW_PtLblCarBef3;
	wpArrLblCarBef	[3] = ABW_PtLblCarBef4;

	wpArrLblCarAft	[0] = ABW_PtLblCarAft1;
	wpArrLblCarAft	[1] = ABW_PtLblCarAft2;
	wpArrLblCarAft	[2] = ABW_PtLblCarAft3;
	wpArrLblCarAft	[3] = ABW_PtLblCarAft4;

	wpArrLblObst	[0] = ABW_PtElpObst1;
	wpArrLblObst	[1] = ABW_PtElpObst2;
	wpArrLblObst	[2] = ABW_PtElpObst3;
	wpArrLblObst	[3] = ABW_PtElpObst4;

	wpArrLblID		[0] = ABW_PtLblID1;
	wpArrLblID		[1] = ABW_PtLblID2;
	wpArrLblID		[2] = ABW_PtLblID3;
	wpArrLblID		[3] = ABW_PtLblID4;

	wpArrLblCash	[0] = ABW_PtLblCash1;
	wpArrLblCash	[1] = ABW_PtLblCash2;
	wpArrLblCash	[2] = ABW_PtLblCash3;
	wpArrLblCash	[3] = ABW_PtLblCash4;

	wpArrLblTkt		[0] = ABW_PtLblTkt1;
	wpArrLblTkt		[1] = ABW_PtLblTkt2;
	wpArrLblTkt		[2] = ABW_PtLblTkt3;
	wpArrLblTkt		[3] = ABW_PtLblTkt4;

	wpArrLblVoice	[0] = ABW_PtLblVoice1;
	wpArrLblVoice	[1] = ABW_PtLblVoice2;
	wpArrLblVoice	[2] = ABW_PtLblVoice3;
	wpArrLblVoice	[3] = ABW_PtLblVoice4;

	wpArrLblMnt		[0] = ABW_PtLblMnt1;
	wpArrLblMnt		[1] = ABW_PtLblMnt2;
	wpArrLblMnt		[2] = ABW_PtLblMnt3;
	wpArrLblMnt		[3] = ABW_PtLblMnt4;

	////////// G -> S	//////////
	wpArrLblArmDN	[0]	= ABW_PtLblArmDN1;
	wpArrLblArmDN	[1]	= ABW_PtLblArmDN2;
	wpArrLblArmDN	[2]	= ABW_PtLblArmDN3;
	wpArrLblArmDN	[3]	= ABW_PtLblArmDN4;

	wpArrLblArmUP	[0]	= ABW_PtLblArmUP1;
	wpArrLblArmUP	[1]	= ABW_PtLblArmUP2;
	wpArrLblArmUP	[2]	= ABW_PtLblArmUP3;
	wpArrLblArmUP	[3]	= ABW_PtLblArmUP4;

	wpArrLblDisp	[0]	= ABW_PtLblDisp1;
	wpArrLblDisp	[1]	= ABW_PtLblDisp2;
	wpArrLblDisp	[2]	= ABW_PtLblDisp3;
	wpArrLblDisp	[3]	= ABW_PtLblDisp4;

	return;
}

void MsgGUIDisplay (u8 ui_msgid, u32 ui_data_len, msg_data_buf_t buf_data)
{
	char dispMsg [122+1];
	PtWidget_t * widget = NULL;
	int n_args=0;
	PtArg_t args [5];
	u32 eval;
	u32 fld1, fld2;
	u32 gantryID;

	gantryID = (int) (buf_data[0] & 0x07);

	if (gantryID >= MAX_DISPLAY_GANTRYs)
	{
		print ("GUI available for only %d gantries.\n",MAX_DISPLAY_GANTRYs);
		return;
	}

	eval = PtEnter (0);
    if (eval < 0 && eval != -EDEADLK)
    {
    	print ("Could not lock photon lib\n");
    	return;
    }

    ////after this point in function DO NOT RETURN before call to PtLeave(..)////

    switch (ui_msgid)
	{
    	////////////////////		SIMU  -->  Gantry messages		////////////////////
		case _EZCP_02:	//Vehicle sensor
			//show/erase car before/after

			fld1 = ParseBits(buf_data, 4, 2);
			if ( fld1 & 0x02 )	//After gantry
				widget = wpArrLblCarAft [gantryID];
			else				//Before gantry
				widget = wpArrLblCarBef [gantryID];

			if (!(fld1 & 0x01))	{//Not present

				PtSetArg( &args[1], Pt_ARG_FILL_COLOR, fillClrNOCAR, 0 );
				PtSetArg( &args[2], Pt_ARG_TEXT_STRING, NULL, 0 );
			}
			else {
				PtSetArg( &args[1], Pt_ARG_FILL_COLOR, fillClrCAR, 0 );
				PtSetArg( &args[2], Pt_ARG_TEXT_STRING, "CAR", 0 );
			}
			n_args = 3;

			break;

		case _EZCP_03:	//Obstacle Sensor
			//Show obstacle red dot
			fld1 = ParseBits (buf_data, 4, 1);	//Obstacle Detected
			print ("Obstacle Detected [%d]\n", fld1);

			if (0 != fld1)
				PtSetResource(wpArrLblObst [gantryID], Pt_ARG_INSIDE_COLOR, fillClrOBST, 0 );
			else
				PtSetResource(wpArrLblObst [gantryID], Pt_ARG_INSIDE_COLOR, fillClrNOOBST, 0 );
			break;

		case _EZCP_04:	//From antenna
			//show IU label and cash [as text]
			fld1 = ParseBits (buf_data, 4, 13);	//IU label
			fld2 = ParseBits (buf_data, 17, 12);//Cash avail

			if (fld1 > 0)
			{
				sprintf (dispMsg, "IU  %x", fld1);
				PtSetResource( wpArrLblID [gantryID], Pt_ARG_TEXT_STRING, dispMsg, 0 );
				sprintf (dispMsg, "$ %x.%x", (fld2>>4), (fld2&0xf));
				PtSetResource( wpArrLblCash [gantryID], Pt_ARG_TEXT_STRING, dispMsg, 0 );
			}
			else
			{
				PtSetResource( wpArrLblID [gantryID], Pt_ARG_TEXT_STRING, NULL, 0 );
				PtSetResource( wpArrLblCash [gantryID], Pt_ARG_TEXT_STRING, NULL, 0 );
			}
			break;

		case _EZCP_06:	//From cashcard reader
			//show card label and cash [as text]
			fld1 = ParseBits (buf_data, 4, 13);	//CC label
			fld2 = ParseBits (buf_data, 17, 12);//Cash avail

			if (fld1 > 0)
			{
				sprintf (dispMsg, "CC  %x", fld1);
				PtSetResource( wpArrLblID [gantryID], Pt_ARG_TEXT_STRING, dispMsg, 0 );
				sprintf (dispMsg, "$ %x.%x", (fld2>>4), (fld2&0xf));
				PtSetResource( wpArrLblCash [gantryID], Pt_ARG_TEXT_STRING, dispMsg, 0 );
			}
			else
			{
				PtSetResource( wpArrLblID [gantryID], Pt_ARG_TEXT_STRING, NULL, 0 );
				PtSetResource( wpArrLblCash [gantryID], Pt_ARG_TEXT_STRING, NULL, 0 );
			}
			break;

		case _EZCP_08:	//From complimentary card reader
			//show card label [as text]
			fld1 = ParseBits (buf_data, 4, 13);	//CompC label

			if (fld1 > 0)
			{
				sprintf (dispMsg, "C   %x", fld1);
				PtSetResource( wpArrLblID [gantryID], Pt_ARG_TEXT_STRING, dispMsg, 0 );
				PtSetResource( wpArrLblCash [gantryID], Pt_ARG_TEXT_STRING, NULL, 0 );
			}
			else
			{
				PtSetResource( wpArrLblID [gantryID], Pt_ARG_TEXT_STRING, NULL, 0 );
				PtSetResource( wpArrLblCash [gantryID], Pt_ARG_TEXT_STRING, NULL, 0 );
			}
			break;

		case _EZCP_18:	//From ticket dispenser
			//Show ticket-request blue dot
			fld1 = ParseBits (buf_data, 4, 1);	//Request for ticket
			if (fld1 > 0)
			{
				PtSetResource( wpArrLblTkt [gantryID], Pt_ARG_FILL_COLOR, fillPRESSED, 0 );
			}
			else
			{
				PtSetResource( wpArrLblTkt [gantryID], Pt_ARG_FILL_COLOR, fillNOTPRESSED, 0 );
			}
			break;

		case _EZCP_13:	//From attendant support panel
			//Show green/red 'A' [not authorized or authorized, respectively]
			break;

		case _EZCP_14:	//From maintenance support panel
			//Show/hide maintenance image
			fld1 = ParseBits (buf_data, 4, 1);	//1 - Manual
			if (fld1 > 0)
			{
				PtSetResource( wpArrLblMnt [gantryID], Pt_ARG_FILL_COLOR, fillPRESSED, 0 );
			}
			else
			{
				PtSetResource( wpArrLblMnt [gantryID], Pt_ARG_FILL_COLOR, fillNOTPRESSED, 0 );
			}
			break;

		case _EZCP_15:	//From maintenance support panel
			//show maintenance mode number
			fld1 = ParseBits (buf_data, 4, 2);	//Maintenance function
			if (fld1 > 0)
			{
				sprintf (dispMsg, "M %1d", fld1);
				PtSetResource( wpArrLblMnt [gantryID], Pt_ARG_TEXT_STRING, dispMsg, 0 );
				PtSetResource( wpArrLblMnt [gantryID], Pt_ARG_FILL_COLOR, fillPRESSED, 0 );
			}
			else
			{
				PtSetResource( wpArrLblMnt [gantryID], Pt_ARG_TEXT_STRING, "M", 0 );
				PtSetResource( wpArrLblMnt [gantryID], Pt_ARG_FILL_COLOR, fillNOTPRESSED, 0 );
			}
			break;

		case _EZCP_16:	//From building control system
			//show/hide red '[FIRE/POWER] EMERGENCY'
			break;

		case _EZCP_17:	//From voice Intercom
			//Show/hide Intercom image
			fld1 = ParseBits (buf_data, 4, 1);	//Request for Attendant help
			if (fld1 > 0)
			{
				PtSetResource( wpArrLblVoice [gantryID], Pt_ARG_FILL_COLOR, fillPRESSED, 0 );
			}
			else
			{
				PtSetResource( wpArrLblVoice [gantryID], Pt_ARG_FILL_COLOR, fillNOTPRESSED, 0 );
			}
			break;
    	/////////////////////////////////////////////////////////////////////////////

    	///////////////////////////// Gantry --> Simu  //////////////////////////////
		case _EZCP_01:	//To Gantry Arm
			//show/hide UP/DOWN ARM
			fld1 = ParseBits(buf_data, 4, 1);	//Direction
			fld2 = ParseBits(buf_data, 5, 4);	//Spare [Partial close]
			print ("Gantry Arm UP [%d]\n", fld1);
			if (0 != fld1)	//UP
			{
				PtSetResource(wpArrLblArmDN [gantryID], Pt_ARG_FILL_COLOR, fillClrNOARMDN, 0 );
				//PtSetResource(wpArrLblArmDN [gantryID], Pt_ARG_FLAGS, Pt_HIGHLIGHTED, 0 );
				PtSetResource(wpArrLblArmUP [gantryID], Pt_ARG_FILL_COLOR, fillClrARMUP, 0 );
				//PtSetResource(wpArrLblArmUP [gantryID], Pt_ARG_FLAGS, Pt_HIGHLIGHTED, Pt_HIGHLIGHTED );
			}
			else			//DOWN
			{
				PtSetResource(wpArrLblArmDN [gantryID], Pt_ARG_FILL_COLOR, fillClrARMDN, 0 );
				//PtSetResource(wpArrLblArmDN [gantryID], Pt_ARG_FLAGS, Pt_HIGHLIGHTED, Pt_HIGHLIGHTED );
				PtSetResource(wpArrLblArmUP [gantryID], Pt_ARG_FILL_COLOR, fillClrNOARMUP, 0 );
				//PtSetResource(wpArrLblArmUP [gantryID], Pt_ARG_FLAGS, Pt_HIGHLIGHTED, 0 );
			}
			break;

		case _EZCP_05:
		case _EZCP_07:
			//show new cash balance
			fld2 = ParseBits(buf_data, 5, 12);	//New Cash balance
			sprintf (dispMsg, "$ %x.%x", (fld2>>4), (fld2&0xf));
			PtSetResource( wpArrLblCash [gantryID], Pt_ARG_TEXT_STRING, dispMsg, 0 );
			break;

		case _EZCP_10:	//To display
			buf_data [EZCP_MAX_DATA_LEN-1] = '\0';
			PtSetResource( wpArrLblDisp [gantryID], Pt_ARG_TEXT_STRING, buf_data+1, 0 );
			break;

		case _EZCP_11:	//To ticket dispenser
			break;

    	/////////////////////////////////////////////////////////////////////////////
		default:
			break;
	}

    if (n_args > 0 && (NULL != widget))
    {
        //PtSetResource( ABW_PtLabel1, Pt_ARG_TEXT_STRING, dispMsg, 0 );
    	PtSetResources (widget, n_args, args);
    	//sleep (1);
    }

	PtLeave (eval);
	return;
}

int ParseBits(msg_data_buf_t buf, int Start, int Length)
{
	int i = 0;
	long message_value = 0;
	int mask;
    int some = 0;
	for(i = 0; i < 4; i++)
	{
		some = pow((double)256,(double)i);
        message_value += buf[i] * some ;
	}


	message_value = message_value >> (Start-1);


	mask = pow((double)2,(double)Length)-1;

	message_value = message_value & mask;

	return message_value;

}

unsigned char nibbleSwap(unsigned char a)
{
	return (a<<4) | (a>>4);
}
